package whr.modules.interview.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import whr.common.exception.Exception;
import whr.common.utils.PageUtils;
import whr.common.utils.Query;
import whr.modules.interview.dao.InterviewRecordsDao;
import whr.modules.interview.dao.MinzuDao;
import whr.modules.interview.dao.StationDao;
import whr.modules.interview.entity.InterviewRecordsEntity;
import whr.modules.interview.entity.dto.CheckResultDto;
import whr.modules.interview.entity.dto.InterviewResultDto;
import whr.modules.interview.entity.vo.TurnoverReportVo;
import whr.modules.interview.service.InterviewRecordsService;
import whr.modules.sys.dao.SysOrganizationsMapper;
import whr.modules.sys.dao.SysRoleDao;
import whr.modules.sys.dao.SysUserDao;
import whr.modules.sys.dao.SysUserRoleDao;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.util.*;
import java.util.stream.Collectors;

@Slf4j

@Service("interviewRecordsService")
public class InterviewRecordsServiceImpl extends ServiceImpl<InterviewRecordsDao, InterviewRecordsEntity> implements InterviewRecordsService {

    @Autowired
    private MinzuDao minzuDao;

    @Autowired
    private StationDao stationDao;

    @Autowired
    private SysUserDao sysUserDao;

    @Autowired
    private SysRoleDao sysRoleDao;

    @Autowired
    private SysUserRoleDao sysUserRoleDao;

    @Autowired
    private SysOrganizationsMapper sysOrganizationsMapper;

    @Autowired
    private InterviewRecordsDao interviewRecordsDao;

    @Override
    public PageUtils queryPage(Map<String, Object> params) {

        // 1.获取params参数中的用户Id
        Long userId = (Long) params.get("userId");

        // 2.判断当前用户是否为面试官
        List<Long> roleIdList = sysUserRoleDao.queryRoleIdList(userId);

        // 2.1 查询面试官的角色Id
        Long interviewRoleId = sysRoleDao.getInterviewreId("面试官");


        IPage<InterviewRecordsEntity> page = this.page(
                new Query<InterviewRecordsEntity>().getPage(params),
                new QueryWrapper<InterviewRecordsEntity>()
                        .like(!StringUtils.isEmpty(params.get("key")), "name", params.get("key"))
                        // 只有当前登录的用户角色为面试官 才进行eq判断
                        // TODO 不能考虑一个用户包含多个角色 比如同时具有人事主管和面试官的情况
                        .eq(roleIdList.contains(interviewRoleId),"interviewer", userId)
                        // 当登录角色为面试官时 只显示等待录入结果的记录
                        .eq(roleIdList.contains(interviewRoleId),"flow_status", 0)
                        // 添加一个排序条件 按照最新的创建时间排序
                        .orderByDesc("create_time")
        );

        // 封装 民族 应聘岗位 面试官姓名信息 创建人姓名 使用stream流
        List<InterviewRecordsEntity> collect = page.getRecords().stream().map(entity -> {
            entity.setMinzu(minzuDao.getMinzuName(entity.getMinzu()));
            entity.setStation(stationDao.getStationName(entity.getStation()));
//            entity.setInterviewer(sysUserDao.queryInterviewer(Long.valueOf(entity.getInterviewer())));
            entity.setCreateUser(sysUserDao.queryInterviewer(Long.valueOf(entity.getCreateUser())));
            if (entity.getEntryOrganization() != null){
                entity.setEntryOrganization(sysOrganizationsMapper.getOrganizationName(Integer.valueOf(entity.getEntryOrganization())));
            }
            return entity;
        }).collect((Collectors.toList()));

        page.setRecords(collect);
        return new PageUtils(page);
    }

    /*
    * 录入面试结果
    * */
    @Override
    public void addInterviewResult(InterviewResultDto interviewResultDto) {
        try {
            // 1.通过Id获取面试记录
            InterviewRecordsEntity interviewRecordsEntity = this.getById(interviewResultDto.getInterviewId());

            // 2.设置面试结果
            interviewRecordsEntity.setSignIn(interviewResultDto.getSignIn());
            interviewRecordsEntity.setSignInTime(interviewResultDto.getSignInTime());
            interviewRecordsEntity.setMinPay(interviewResultDto.getMinPay());
            interviewRecordsEntity.setInterviewScore(interviewResultDto.getInterviewScore());
            interviewRecordsEntity.setInterviewStatus(interviewResultDto.getInterviewStatus());

            // 3.设置当前结果的审核时间
            interviewRecordsEntity.setInterviewTime(new Date());

            // 当面试状态为未通过 流程状态设置为 未通过面试
            if(interviewResultDto.getInterviewStatus() == 0){
                interviewRecordsEntity.setFlowStatus(interviewRecordsEntity.getFlowStatus() + 1);
            }else {
                // 4. 设置当前面试记录的流程状态 为 等待录取审核
                interviewRecordsEntity.setFlowStatus(interviewRecordsEntity.getFlowStatus() + 2);
            }

            // 5.调用修改的方法
            this.updateById(interviewRecordsEntity);
        } catch (Exception e) {
            throw new Exception("录入面试结果失败");
        }
    }

    /*
    * 录取审核
    * */
    @Override
    public void checkResult(CheckResultDto checkResultDto) {
        try {
            // 1.通过面试记录Id获取面试记录
            InterviewRecordsEntity interviewRecordsEntity = this.getById(checkResultDto.getInterviewId());
            log.info("审核为{}",checkResultDto);
            // 2.设置审核结果
            interviewRecordsEntity.setEnrollStatus(checkResultDto.getEnrollStatus());

            if (checkResultDto.getEnrollTime() != null){
                interviewRecordsEntity.setEnrollTime(checkResultDto.getEnrollTime());
            }

            // 判断参数是否为空
            interviewRecordsEntity.setEntryStatus(checkResultDto.getEntryStatus());

            if (checkResultDto.getEntryTime() != null){
                interviewRecordsEntity.setEntryTime(checkResultDto.getEntryTime());
            }

            if (checkResultDto.getNotEmployReason() != null){
                interviewRecordsEntity.setNotEmployReason(checkResultDto.getNotEmployReason());
            }

            if (checkResultDto.getEntryOrganization() != null){
                interviewRecordsEntity.setEntryOrganization(checkResultDto.getEntryOrganization().toString());
            }

            // 3.设置当前面试记录的流程状态 为 完成录取审核
            interviewRecordsEntity.setFlowStatus(interviewRecordsEntity.getFlowStatus() + 1);

            // 4.调用修改的方法
            this.updateById(interviewRecordsEntity);
        } catch (Exception e) {
            throw new Exception("录取审核失败");
        }

    }

    /*
    * 获取历史面试记录
    * */
    @Override
    public InterviewRecordsEntity getHistory(Map<String, Object> params) {
        try {
            // 1.获取参数
            String name = (String) params.get("name");
            String phone = (String) params.get("phone");
            String createTime = (String) params.get("createTime");
            SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
            Date date = simpleDateFormat.parse(createTime);

            // 2.通过姓名和电话获取面试记录
            LambdaQueryWrapper<InterviewRecordsEntity> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(InterviewRecordsEntity::getName, name);
            queryWrapper.eq(InterviewRecordsEntity::getPhone, phone);
            // 小于当前的创建时间
            queryWrapper.lt(InterviewRecordsEntity::getCreateTime, date);

            // 3.调用查询方法
            List<InterviewRecordsEntity> historyList = this.list(queryWrapper);

            // 3.1 判断历史面试记录是否为空
            if (ObjectUtils.isEmpty(historyList)){
                return null;
            }

            // 3.2 只获取当前时间的上一条面试记录 (即当前集合的第一条数据)
            InterviewRecordsEntity history = historyList.get(0);

            // 4 封装创建人的姓名 以及应聘岗位信息
            history.setCreateUser(sysUserDao.queryInterviewer(Long.valueOf(history.getCreateUser())));
            history.setStation(stationDao.getStationName(history.getStation()));

            return history;
        } catch (ParseException e) {
            throw new RuntimeException(e);
        }
    }


    /*
    * 获取面试者面试评分分布
    * */
    @Override
    public List<Integer> getScoreCount() {
        // 1.创建一个集合用于存放数据
        List<Integer> scoreCount = new ArrayList<>(4);
        for (int i = 0; i < 4; i++) {
            scoreCount.add(0); // 添加4个值为0的Integer对象到列表中
        }
        // 1.1 创建一个map集合
        HashMap<String, Object> maps = new HashMap<>();
        // 2.mapper层先根据面试分值分组并查询
        List<Map<String, Integer>> list = interviewRecordsDao.selectScoreCount();
        // 3.遍历list中的数据
        for (Map<String, Integer> map : list) {
            //System.out.println(map.keySet());// [interview_score, count_of_scores]
            for (String name : map.keySet()) {
                if (name.equals("interview_score")){
                    maps.put(map.get(name).toString(),map.get("count_of_scores"));
                }
            }
        }

        // 3.1 获取优秀的数据
//        System.out.println(maps); // {85=3, 75=1, 59=1}
        Long excellentCount = (Long) maps.get("95");
//        System.out.println(excellentCount);
        if (excellentCount != null){
            scoreCount.set(0,excellentCount.intValue());
        }
        // 3.2 获取良好的数据
        Long goodCount = (Long) maps.get("85");
        if (goodCount != null){
            scoreCount.set(1,goodCount.intValue());
        }
        // 3.3 获取一般的数据
        Long commonCount = (Long) maps.get("75");
        if (commonCount != null){
            scoreCount.set(2,commonCount.intValue());
        }
        // 3.4 获取差的数据
        Long badCount = (Long) maps.get("59");
        if (badCount != null){
            scoreCount.set(3,badCount.intValue());
        }
        return scoreCount;
    }

    /*
    * 获取近七天的新增面试记录
    * */
    @Override
    public TurnoverReportVo getTurnover() {

        // 获取当日的日期
        LocalDate today = LocalDate.now();

        // 创建一个存储时间的集合
        ArrayList<LocalDate> dataList = new ArrayList<>();
        dataList.add(today);

        // 循环获取前6天的日期
        for (int i = 1; i < 7; i++) {
            dataList.add(0,today.minusDays(i));
        }

        // 创建一个存储数据的集合
        ArrayList<Integer> countList = new ArrayList<>();
        // 遍历日期时间集合
        for (LocalDate localDate : dataList) {
            LocalDateTime beginTime = LocalDateTime.of(localDate, LocalTime.MIN);
            LocalDateTime endTime = LocalDateTime.of(localDate, LocalTime.MAX);
            // 封转查询条件
            Map map = new HashMap();
            map.put("beginTime",beginTime);
            map.put("endTime",endTime);
            Integer count = interviewRecordsDao.countByMap(map);
            countList.add(count);
        }

        // 数据封转
        return new TurnoverReportVo(dataList,countList);
    }


    @Override
    public Object getWaitingCount() {
        return interviewRecordsDao.getUserCount();
    }


}